package cn.itsnkkka.utils;


import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateDeserializer;
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateTimeDeserializer;
import com.fasterxml.jackson.datatype.jsr310.deser.LocalTimeDeserializer;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalTimeSerializer;
import org.springframework.beans.BeanUtils;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.util.List;

public class JSONUtils {

    private static final ObjectMapper objectMapper = new ObjectMapper();


    static {
        //解决序列化localdatetime格式问题
        initRegisterModule();
    }

    public static ObjectMapper getObjectMapper() {
        return objectMapper;
    }

    /**
     *  对象转string
     * @param o 对象
     * @return string
     * @throws JsonProcessingException 异常
     */
    public static String toJSONString(Object o ) throws JsonProcessingException {
        return  objectMapper.writeValueAsString(o);
    }

    public static void  initRegisterModule(){

        JavaTimeModule javaTimeModule = new JavaTimeModule();

        javaTimeModule.addSerializer(LocalDateTime.class, new LocalDateTimeSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
        javaTimeModule.addSerializer(LocalDate.class, new LocalDateSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));

        javaTimeModule.addSerializer(LocalTime.class, new LocalTimeSerializer(DateTimeFormatter.ofPattern("HH:mm:ss")));
        javaTimeModule.addDeserializer(LocalDateTime.class, new LocalDateTimeDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));

        javaTimeModule.addDeserializer(LocalDate.class, new LocalDateDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
        javaTimeModule.addDeserializer(LocalTime.class, new LocalTimeDeserializer(DateTimeFormatter.ofPattern("HH:mm:ss")));

        objectMapper.registerModule(javaTimeModule);

    }

    /**
     *
     * 解析
     * @param t 泛型
     * @param json json
     * @param <T>  泛型
     * @return 对象
     * @throws JsonProcessingException
     */
    public static <T> T parse(Class<T> t,String json) throws JsonProcessingException {

        return objectMapper.readValue(json, t);
    }


    public static <T> List<T> parse(String json,TypeReference<List<T>> valueTypeRef ) throws JsonProcessingException {

        return objectMapper.readValue(json, valueTypeRef);
    }

    public static <T> T parseObject(String json,TypeReference<T> valueTypeRef ) throws JsonProcessingException {

        return objectMapper.readValue(json, valueTypeRef);
    }


    public static void copyJSONProperty(Object source, Object target){
        try {
            String sourceJSON = toJSONString(source);
            Object parseResult = parse(target.getClass(), sourceJSON);
            BeanUtils.copyProperties(parseResult, target);
        } catch (JsonProcessingException e) {
            throw new RuntimeException(e);
        }
    }

    public static JsonNode toNode(String body) throws JsonProcessingException {

        return objectMapper.readTree(body);

    }

}